import java.util.ArrayList;


public class Perceptron {

	private final double LR = 1;
	private ArrayList<ArrayList<Double>> examples;
	private ArrayList<Double> weights;
	private int exampleSize = 0;
	double threshold = 0;
	public Perceptron(ArrayList<ArrayList<Double>> examples)
	{
		if(!examples.isEmpty())
			exampleSize = examples.get(0).size() - 1;
		this.examples = examples;
		System.out.println(exampleSize);
		weights = new ArrayList<Double>(exampleSize);
		for(int i = 0; i < exampleSize; i++)
			weights.add(0.0);
	}
	
	public void LearnAlg()
	{
		
		while(hasError())
		//for(int k=0;k<20;k++)
		{
			for(int i = 0; i < examples.size(); i++)
			{
				int output = calcOutput(i);
				System.out.println(i+"!"+output);
				int target = (int) Math.round((examples.get(i).get(exampleSize)));
				for(int j = 0 ; j < exampleSize; j++)
				{
					double newWeight = weights.get(j) + LR * (target - output) * examples.get(i).get(j);
					weights.set(j, newWeight);
					System.out.println("new "+j+" "+newWeight);
				}
				
				//threshold = threshold + LR * (output - target);
			}
		}
		
		for(double w:weights)
			System.out.println("weight " +w);
	}
	
	public boolean hasError()
	{
		for(int i = 0; i < examples.size(); i++)
		{
			System.out.println(calcOutput(i) +" "+examples.get(i).get(exampleSize) );
			if(calcOutput(i) != examples.get(i).get(exampleSize))
				return true;
		}
		return false;
	}
	public int calcOutput(int exampleNum)
	{
		double result = 0;
		for(int j = 0; j < exampleSize; j++)
		{
			result += weights.get(j) * examples.get(exampleNum).get(j);
		}
		
		return ((result > threshold) ? 1 : 0);
	}
}
